
#include "ParticleManager.h"
#include "Emitter.h"
#include "..\\..\\TinyXML\tinyxml.h"
#include "..\\..\SGD Wrappers\SGD_GraphicsManager.h"

#include "..\Definitions.h"

ParticleManager::ParticleManager()
{
}


ParticleManager::~ParticleManager()
{
	for (unsigned int i = 0; i < emitters.size(); i++)
	{
		if (emitters[i]->GetFlyweight().GetImage() != SGD::INVALID_HANDLE)
		{
			SGD::GraphicsManager::GetInstance()->UnloadTexture(emitters[i]->GetFlyweight().GetImage());
		}
		delete emitters[i];
	}
}

Emitter* ParticleManager::operator[](unsigned int index)
{
	return emitters[index];
}

void ParticleManager::Render()
{
	for (unsigned int i = 0; i < emitters.size(); ++i)
	{
		emitters[i]->Render();
	}
}

void ParticleManager::Update(float dt)
{
	for (unsigned int i = 0; i < emitters.size(); ++i)
	{
		emitters[i]->Update(dt);
	}
}

void ParticleManager::LoadEmitters(char * fileName)
{
	TiXmlDocument doc;

	if (doc.LoadFile(fileName))
	{
		TiXmlElement* pRoot = doc.RootElement();

		if (pRoot != nullptr)
		{
			TiXmlElement* pEntity;

			pEntity = pRoot->FirstChildElement("Emitter");

			int tempInt;
			double tempDouble;
			double tempDouble2;
			double tempDouble3;
			double tempDouble4;

			for (int i = 0; pEntity != nullptr; ++i)
			{
				emitters.push_back(new Emitter());

				emitters[i]->SetEmitterName(pEntity->Attribute("EmitterName"));
				std::string path = "Resource\\";
				std::string file = pEntity->Attribute("EmitterFile");
				path += file;
				emitters[i]->SetFileName(path.c_str());
				pEntity->Attribute("MaxParticles", &tempInt);
				emitters[i]->SetMaxParticles(tempInt);
				pEntity->Attribute("SpawnRate", &tempDouble);
				emitters[i]->SetSpawnRate((float)tempDouble);
				if (!strcmp(pEntity->Attribute("Repeat"), "true"))
					emitters[i]->SetRepeat(true);
				else
					emitters[i]->SetRepeat(false);
				pEntity = pEntity->FirstChildElement("Normal");
				pEntity->Attribute("X", &tempDouble);
				pEntity->Attribute("Y", &tempDouble2);
				emitters[i]->SetNormal(SGD::Vector((float)tempDouble, (float)tempDouble2));

				// Flyweight
				pEntity = pEntity->NextSiblingElement("Flyweight");
				pEntity->Attribute("EmitterType", &tempInt);
				emitters[i]->GetFlyweight().SetEmitterType(tempInt);
				pEntity->Attribute("EmitterAngle", &tempDouble);
				tempDouble = (SGD::PI / 180) * tempDouble;
				emitters[i]->GetFlyweight().SetAngle((float)tempDouble);
				pEntity->Attribute("EmitterWidth", &tempInt);
				emitters[i]->GetFlyweight().SetEmitterWidth(tempInt);
				pEntity->Attribute("EmitterHeight", &tempInt);
				emitters[i]->GetFlyweight().SetEmitterHeight(tempInt);
				pEntity->Attribute("RotationRate", &tempDouble);
				emitters[i]->GetFlyweight().SetRotationRate((float)tempDouble);
				pEntity->Attribute("EmitterRange", &tempInt);
				emitters[i]->GetFlyweight().SetEmitterRange(tempInt);

				pEntity->Attribute("EmitterMinLife", &tempDouble);
				emitters[i]->GetFlyweight().SetMinLife((float)tempDouble);
				pEntity->Attribute("EmitterMaxLife", &tempDouble);
				emitters[i]->GetFlyweight().SetMaxLife((float)tempDouble);
				pEntity->Attribute("StartScale", &tempDouble);
				emitters[i]->GetFlyweight().SetStartScale((float)tempDouble);
				pEntity->Attribute("EndScale", &tempDouble);
				emitters[i]->GetFlyweight().SetEndScale((float)tempDouble);
				pEntity->Attribute("StartSpeed", &tempDouble);
				emitters[i]->GetFlyweight().SetStartSpeed((float)tempDouble);
				pEntity->Attribute("EndSpeed", &tempDouble);
				emitters[i]->GetFlyweight().SetEndSpeed((float)tempDouble);
				pEntity->Attribute("ParticleWeight", &tempDouble);
				emitters[i]->GetFlyweight().SetWeight((float)tempDouble);

				if (!strcmp(pEntity->Attribute("Gravity"), "true"))
					emitters[i]->GetFlyweight().SetGravity(true);
				else
					emitters[i]->GetFlyweight().SetGravity(false);

				if (!strcmp(pEntity->Attribute("Wind"), "true"))
					emitters[i]->GetFlyweight().SetWind(true);
				else
					emitters[i]->GetFlyweight().SetWind(false);

				pEntity = pEntity->FirstChildElement("DrawRect");
				pEntity->Attribute("Left", &tempDouble);
				pEntity->Attribute("Top", &tempDouble2);
				pEntity->Attribute("Width", &tempDouble3);
				pEntity->Attribute("Height", &tempDouble4);
				emitters[i]->GetFlyweight().SetDrawRect((float)tempDouble, (float)tempDouble2, (float)(tempDouble + tempDouble3), (float)(tempDouble2 + tempDouble4));

				pEntity = pEntity->NextSiblingElement("CenterPoint");
				pEntity->Attribute("X", &tempDouble);
				pEntity->Attribute("Y", &tempDouble2);
				emitters[i]->GetFlyweight().SetCenterPoint(SGD::Vector((float)tempDouble, (float)tempDouble2));

				pEntity = pEntity->NextSiblingElement("StartColor");
				pEntity->Attribute("A", &tempDouble);
				pEntity->Attribute("R", &tempDouble2);
				pEntity->Attribute("G", &tempDouble3);
				pEntity->Attribute("B", &tempDouble4);
				emitters[i]->GetFlyweight().SetStartColorA((float)tempDouble);
				emitters[i]->GetFlyweight().SetStartColorR((float)tempDouble2);
				emitters[i]->GetFlyweight().SetStartColorG((float)tempDouble3);
				emitters[i]->GetFlyweight().SetStartColorB((float)tempDouble4);

				pEntity = pEntity->NextSiblingElement("EndColor");
				pEntity->Attribute("A", &tempDouble);
				pEntity->Attribute("R", &tempDouble2);
				pEntity->Attribute("G", &tempDouble3);
				pEntity->Attribute("B", &tempDouble4);
				emitters[i]->GetFlyweight().SetEndColorA((float)tempDouble);
				emitters[i]->GetFlyweight().SetEndColorR((float)tempDouble2);
				emitters[i]->GetFlyweight().SetEndColorG((float)tempDouble3);
				emitters[i]->GetFlyweight().SetEndColorB((float)tempDouble4);

				pEntity = pEntity->Parent()->Parent()->NextSiblingElement("Emitter");
			}
		}
	}
	for (unsigned int i = 0; i < emitters.size(); ++i)
	{
		emitters[i]->Load();
		emitters[i]->GetFlyweight().SetImage(GRAPHICS->LoadTexture(emitters[i]->GetFileName()));
	}

}